package com.puzzlebazar.client.main.view;

import java.util.Iterator;

import com.google.gwt.user.client.ui.Composite;
import com.google.gwt.user.client.ui.DisclosurePanel;
import com.google.gwt.user.client.ui.HasWidgets;
import com.google.gwt.user.client.ui.VerticalPanel;
import com.google.gwt.user.client.ui.Widget;
import com.puzzlebazar.client.main.model.AutoLink;
import com.puzzlebazar.client.main.model.LinkGroup;
import com.puzzlebazar.client.user.UserModel;
import com.puzzlebazar.client.util.AutoHyperlink;
import com.puzzlebazar.client.util.Observable;
import com.puzzlebazar.client.util.Observer;

public class LinkGroupsView extends Composite implements Observer, UpdateTokenCallback{

	private final UserModel model;

	private final VerticalPanel mainPanel = new VerticalPanel();
	
	/**
	 * Creates a view into a group of links
	 * 
	 * @param model The model to associate with this view
	 */
	public LinkGroupsView( UserModel model ) {
		super();
		
		this.model = model;
		model.addObserver( this );
		
		mainPanel.setStylePrimaryName( "linkGroupsView" );
		mainPanel.setWidth( "100%" );
		initWidget( mainPanel );
	}
	
	
	@Override
	public void update(Observable observable, Object arg) {
		assert( observable == model );
		updateWidget();
	}


	/**
	 * Updates all the widgets contained in the link group panel
	 */
	private void updateWidget() {
		
		mainPanel.clear();
		
		for( int i=0; i < model.getLinkGroupCount(); ++i ) {
			LinkGroup linkGroup = model.getLinkGroup(i);
		
				
			VerticalPanel linkGroupPanel = new VerticalPanel();
			for( int j=0; j < linkGroup.getLinkCount(); ++j ) {
				AutoLink link = linkGroup.getLink(j); 
				AutoHyperlink hyperlink = new AutoHyperlink( link.getText(), link.getTokenFactory() );
				linkGroupPanel.add( hyperlink );
			}
			if( i == 0 ) {
				VerticalPanel defaultLinkGroup = new VerticalPanel();
				defaultLinkGroup.setStylePrimaryName( "defaultLinkGroupPanel" );
				defaultLinkGroup.add( linkGroupPanel );
				mainPanel.add( defaultLinkGroup );
			}
			else
			{
				DisclosurePanel linkGroupDisclosure = new DisclosurePanel( linkGroup.getName() );			
				linkGroupDisclosure.setStylePrimaryName( "linkGroupPanel" );
				linkGroupDisclosure.setOpen(true);
				linkGroupDisclosure.setContent( linkGroupPanel );			
				mainPanel.add( linkGroupDisclosure );
			}
		}		
		
	}

	@Override
	public void updateTokens() {
		
		Widget widget;
		for( int i=0; i < mainPanel.getWidgetCount(); ++i ) {
			// Top-level should be a container (Disclosure panel or Vertical panel)
			widget = mainPanel.getWidget(i);
			if( !(widget instanceof HasWidgets) ) continue;
			
			// Mid-level should be another container (VerticalPanel)
			widget = ((HasWidgets)widget).iterator().next();
			if( !(widget instanceof HasWidgets) ) continue;
			
			for (Iterator<Widget> iterator = ((HasWidgets)widget).iterator(); iterator.hasNext();) {
				// Low-level should be an auto hyperlink
				widget = iterator.next();
				if( !(widget instanceof AutoHyperlink) ) continue;
				((AutoHyperlink)widget).updateTokens();				
			}
		}
	}


	@Override
	public void release() {
		model.deleteObserver(this);
	}

}
